package com.example.securitydemo.config;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.method.configuration.EnableMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.web.SecurityFilterChain;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;

@Configuration
//@EnableWebSecurity（spring和spring mvc项目要写，spring boot项目可以不写）
@EnableMethodSecurity // 开启基于方法的授权，开启之后才能使用@PreAuthorize注解
public class WebSecurityConfig {

    @Autowired
    private JwtAuthenticationFilter jwtAuthenticationFilter;

    // 修改spring security默认配置
    @Bean
    public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {

        http.httpBasic(AbstractHttpConfigurer::disable) // 禁用明文验证
                .csrf(AbstractHttpConfigurer::disable) // 关闭csrf
                .formLogin(AbstractHttpConfigurer::disable) // 禁用默认登录页
                .logout(AbstractHttpConfigurer::disable) // 禁用默认登出页
                .sessionManagement(session -> session.sessionCreationPolicy(SessionCreationPolicy.STATELESS)); // 禁用session

        http.authorizeHttpRequests(auth ->
                auth
//                        .requestMatchers("/user").permitAll()
                        .anyRequest() // 除了requestMatchers的请求之外，所有请求开启授权保护
                        .authenticated()); // 已认证的请求会被自动授权

        http.formLogin(form ->
                form.loginPage("/login").permitAll() // 无需授权即可访问的页面
                        .successHandler(new DemoAuthenticationSuccessHandler()) // 认证成功时的处理
                        .failureHandler(new DemoAuthenticationFailureHandler()) // 认证失败时的处理
        );

        http.logout(logout ->
                logout.logoutSuccessHandler(new DemoLogoutSuccessHandler()) // 退出登录成功时的处理
        );

        http.exceptionHandling(exception ->
                exception.authenticationEntryPoint(new DemoAuthenticationEntryPoint()) // 未登录时的处理
                        .accessDeniedHandler(new DemoAccessDeniedHandler()) // 请求未授权时的处理
        );

        http.addFilterBefore(jwtAuthenticationFilter, UsernamePasswordAuthenticationFilter.class);
        return http.build();
    }

    /**
     * 基于数据库的{@link DBUserDetailsManager}
     */
    // 创建基于内存的用户管理
//    @Bean
//    public UserDetailsService userDetailsService() {
//        InMemoryUserDetailsManager manager = new InMemoryUserDetailsManager();
//        manager.createUser(
//                User.withDefaultPasswordEncoder()
//                        .username("zcx")
//                        .password("zcx123")
//                        .roles("USER")
//                        .build());
//        return manager;
//    }
}
